#include "httpmgr.h"

HttpMgr::~HttpMgr()
{

}

HttpMgr::HttpMgr()
{
    connect(this,
            &HttpMgr::sig_http_finish,
            this,
            &HttpMgr::slot_http_finish);
}

void HttpMgr::PostHttpReq(QUrl url,
                          QJsonObject json,
                          ReqId req_id,
                          Modules mod)
{
    //因为要发送，所以转换成字节数组
    QByteArray data = QJsonDocument(json).toJson();
    QNetworkRequest request(url);
    request.setHeader(
                QNetworkRequest::ContentTypeHeader,
                "application/json");

    request.setHeader(
                QNetworkRequest::ContentTypeHeader,
                // 由于不同的位数的操作系统对int的存储不一致
                // 当底层默认转换，来换算长度
                QByteArray::number(data.length()));

    // 使用闭包技术，产生的一个智能对象
    //当方法走完，这个对象不会被回收，防止lambda没有执行完成
    //HttpMgr如果被回收，就没有执行lambda的机会了，导致错误
    // 所以这里使用闭包
    // 这里将this指向了一个智能指针，给了self来管理
    auto self = shared_from_this();
    //发送请求，获得回执
    QNetworkReply * reply = _manager.post(
                request,
                data);
    /*
    这里不用this的原因是
    可能会存在HttpMgr被回收的时候
    这个回调还没有调用，等待被回收的时候，这个被调用了
    就会存在问题。
    所以我们使用闭包技术，讲HttpMgr对象交给self来管理
    由于我们使用lambda表示捕获了self，相当于引用+1，所以
    不会被回收。当使用结束后，也会由智能对象来管理回收
    QObject::connect(reply,
                     &QNetworkReply::finished,
                     [this](){

    });
    捕获self其实也是放到了lambda表达式里的成员变量中。
    */
    QObject::connect(reply,
                     &QNetworkReply::finished,
                     [self,reply,
                     req_id,mod](){
        // 处理错误情况
        if(reply->error()!=QNetworkReply::NoError){
            qDebug() << reply->errorString();
            //发送信号通知完成
            emit self->sig_http_finish(
                        req_id,"",
                        ErrorCodes::ERR_NETWORK,
                        mod);
            //回收,建议qt，如果不使用可以回收
            reply->deleteLater();
            return;
        }
        //没错误,将所有回执拿出来
        QString res = reply->readAll();
        //发送信号通知完成
        emit self->sig_http_finish(
                    req_id,res,
                    ErrorCodes::SUCCESS,
                    mod);
        reply->deleteLater();
        return;
    });

}

void HttpMgr::slot_http_finish(ReqId id, QString res, ErrorCodes err, Modules mod)
{
    if(mod==Modules::REGISTERMOD){
        //发送信号通知注册模块信息作出响应
        emit sig_reg_mod_finish(
                    id,
                    res,
                    err);
    }
    if(mod==Modules::RESETMOD){//忘记密码模块
        emit sig_reset_mod_finish(id,
                                  res,
                                  err);
    }
    //登陆模块
    if(mod==Modules::LOGINMOD){
        emit sig_login_mod_finish(id,
                                  res,
                                  err);
    }
}
